package com.caiyi.financial.nirvana.sms.gateway.cmpp;

import com.caiyi.financial.nirvana.sms.gateway.DefaultGateWay;
import io.netty.channel.ChannelDuplexHandler;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.ChannelPromise;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.net.SocketAddress;

public abstract class GatewayControlHandler extends ChannelDuplexHandler {

    private static final Logger logger = LoggerFactory.getLogger(GatewayControlHandler.class);
    protected DefaultGateWay gateWayInfo;
    protected long lastReadTime = 0L;

    @Override
    public void connect(ChannelHandlerContext ctx, SocketAddress remoteAddress, SocketAddress localAddress, ChannelPromise future) {
        logger.info(gateWayInfo.info.getName() + " 通道号：" + gateWayInfo.info.getAccessNumber() + " 建立连接");
        try {
            super.connect(ctx, remoteAddress, localAddress, future);
        } catch (Exception ex) {
            logger.error(ex.getMessage(), ex);
        }
    }

    @Override
    public void close(ChannelHandlerContext ctx, ChannelPromise future) throws Exception {
        logger.info(gateWayInfo.info.getName() + " 通道号：" + gateWayInfo.info.getAccessNumber() + " 正在关闭");
        gateWayInfo.terminating();
        super.close(ctx, future);
    }

    @Override
    public void write(ChannelHandlerContext ctx, Object msg, ChannelPromise promise) throws Exception {
        long timeNow = System.currentTimeMillis();
        if (0 != lastReadTime && timeNow - lastReadTime > 40000) {
            logger.warn(gateWayInfo.info.getName() + " 通道号：" + gateWayInfo.info.getAccessNumber() + " 至少有40秒未接收到服务器数据！");
        }
        super.write(ctx, msg, promise);
    }

    @Override
    public void channelActive(ChannelHandlerContext ctx) throws Exception {
        gateWayInfo.connectSuccess(ctx);
        doLogin(ctx);
        super.channelActive(ctx);
    }

    @Override
    public void channelInactive(ChannelHandlerContext ctx) throws Exception {
        logger.info(gateWayInfo.info.getName() + " 通道号：" + gateWayInfo.info.getAccessNumber() + " 连接断开。");
        gateWayInfo.login = false;
        super.channelInactive(ctx);
    }

    @Override
    public void channelRead(ChannelHandlerContext ctx, Object msg)
            throws Exception {
        lastReadTime = System.currentTimeMillis();
        super.channelRead(ctx, msg);
    }

    //登录
    public abstract void doLogin(ChannelHandlerContext ctx);

    @Override
    public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {
        logger.info("GatewayControlHandler exceptionCaught : {}", cause);
    }

    @Override
    public abstract void userEventTriggered(ChannelHandlerContext ctx, Object evt) throws Exception;
}
